package com.xuequ.answerme.main;

import android.content.ContentValues;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.support.design.widget.Snackbar;
import android.support.v4.app.Fragment;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import android.widget.Toast;

import com.xuequ.answerme.R;
import com.xuequ.answerme.adapter.AllRecyclerViewAdapter;
import com.xuequ.answerme.beans.AnswerBean;
import com.xuequ.answerme.beans.MixQuesAnsBean;
import com.xuequ.answerme.beans.QuestionBean;
import com.xuequ.answerme.beans.UserBean;
import com.xuequ.answerme.databases.MixDBHelper;
import com.xuequ.answerme.details.AnswerDetailActivity;
import com.xuequ.answerme.details.QuestionDetailActivity;
import com.xuequ.answerme.manager.AnswerManager;
import com.xuequ.answerme.manager.QuestionManager;
import com.xuequ.answerme.manager.UserManager;

import java.util.ArrayList;
import java.util.List;
import java.util.Random;

import me.drakeet.materialdialog.MaterialDialog;

/**
 * Created by Shijie on 2015/9/28.
 * <p/>
 * 1、一开始显示20个MixQuesAnsBean
 * 1）先查找缓存，
 * 2）没有缓存就不抓取（提示用户下拉刷新）
 * 2、每次刷新 根据最新一个问题 抓取比此问题还要新的Questions，如果数量>=20，就抓取20个
 */
public class AllFragment extends Fragment {

    private MixDBHelper mixDBHelper;
    private SQLiteDatabase db;

    private View contentView;
    private MaterialDialog materialDialog;
    private TextView OKText;
    private TextView questionPreviewTitle;
    private TextView questionPreviewDesc;
    private TextView detailText;

    private List<MixQuesAnsBean> mData;
    private RecyclerView mRecyclerView;
    private AllRecyclerViewAdapter mAdapter;
    private SwipeRefreshLayout mSwipeRefreshLayout;

    private QuestionManager questionManager;
    private AnswerManager answerManager;
    private UserManager userManager;

    private List<QuestionBean> mQuestionDataToBeShown;
    private List<MixQuesAnsBean> mDataForChange;
    private List<AnswerBean> mRandomAnswerList;// 存储某问题的随机一个答案（可以改成获赞数最高的那个）

    private List<QuestionBean> mOldQuestionDataToBeShown;
    private List<MixQuesAnsBean> mOldDataForChange;
    private List<AnswerBean> mOldRandomAnswerList;

    private QuestionBean mLatestQuestionBean;

    private int onlineRequestForAnswerNew = 0;// 建立一个flag来计算 获取问题所有答案的网络请求 的数量（一开始没有此类网络请求）
    private int onlineRequestForAnswerOld = 0;
    private boolean isGetFromDatabase = true;//建立标志，判断是否发生过下拉刷新新问题
    private boolean isLoadingMore = false;//建立标志，判断当前是否在进行上拉加载

    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_all, container, false);

        initView(view);

        // 寻找最新的十个问题
        firstTimeRefresh();

        return view;
    }

    /**
     * 初始化控件。
     *
     * @param view fragmentView
     */
    private void initView(View view) {

        //打开数据库
        mixDBHelper = new MixDBHelper(getActivity(), "mix.db", null, 1);
        db = mixDBHelper.getWritableDatabase();

        // new一些变量
        mLatestQuestionBean = new QuestionBean();
        mQuestionDataToBeShown = new ArrayList<>();
        mDataForChange = new ArrayList<>();
        mRandomAnswerList = new ArrayList<>();
        mOldDataForChange = new ArrayList<>();
        mOldQuestionDataToBeShown = new ArrayList<>();
        mOldRandomAnswerList = new ArrayList<>();

        if (questionManager == null) {
            questionManager = new QuestionManager();
        }
        if (userManager == null) {
            userManager = new UserManager();
        }
        if (answerManager == null) {
            answerManager = new AnswerManager();
        }


        mSwipeRefreshLayout = (SwipeRefreshLayout) view.findViewById(R.id.all_swipeRefreshLayout);
        //下拉时要做的操作
        mSwipeRefreshLayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
            @Override
            public void onRefresh() {
                findNewQuestions();
            }
        });

        //设置RecycleView的属性
        mRecyclerView = (RecyclerView) view.findViewById(R.id.all_recycler_view);
        RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getActivity());
        mRecyclerView.setLayoutManager(mLayoutManager);
        mRecyclerView.setHasFixedSize(true);

        //List、Adapter和Recycler间的东西
        mData = new ArrayList<>();
        mAdapter = new AllRecyclerViewAdapter(mData);
        mRecyclerView.setAdapter(mAdapter);
        mAdapter.setOnItemClickListener(new AllRecyclerViewAdapter.OnItemClickListener() {
            @Override
            public void onItemTitleClick(View view, int position) {
                // 点击到问题打开QuestionDetailActivity
                Intent intent = new Intent(getActivity(), QuestionDetailActivity.class);
                Bundle bundle = new Bundle();
                bundle.putSerializable("questionBean", mData.get(position).getQuestionBean());
                intent.putExtras(bundle);
                startActivity(intent);
            }

            @Override
            public void onItemTitleLongClick(View view, int position) {
                // 长按问题可预览问题
                previewQuestion(position);
            }

            @Override
            public void onItemContentClick(View view, final int position) {
                // 点击到答案打开QuestionDetailActivity
                Intent intent = new Intent(getActivity(), AnswerDetailActivity.class);
                Bundle bundle = new Bundle();
                bundle.putSerializable("answerBean", mData.get(position).getAnswerBean());
                intent.putExtras(bundle);
                startActivity(intent);
            }
        });

        mAdapter.setOnRefreshDoneListener(new AllRecyclerViewAdapter.OnRefreshDoneListener() {
            @Override
            public void onRefreshDone() {

                if (!isGetFromDatabase) {
                    //如果不是从缓存中获取新的问题（即有进行过下拉刷新问题），就要进行缓存的增删改查

                    //先删除数据库中的所有数据
                    db.execSQL("delete from mix_table");

                    if (mData.size() < 10) {
                        //如果所显示的数据量小于10
                        for (int i = 0; i < mData.size(); i++) {
                            //用contentValues（类似Map：键值对）来存
                            ContentValues contentValues = new ContentValues();

                            contentValues.put("questioner_objectId", mData.get(i).getQuestionBean().getQuestioner().getObjectId());
                            contentValues.put("questioner_name", mData.get(i).getQuestionBean().getQuestioner().getUsername());
                            contentValues.put("question_objectId", mData.get(i).getQuestionBean().getObjectId());
                            contentValues.put("question_title", mData.get(i).getQuestionBean().getQuestion_title());
                            contentValues.put("question_description", mData.get(i).getQuestionBean().getQuestion_description());
                            contentValues.put("question_createdAt", mData.get(i).getQuestionBean().getQuestion_createdAt());
                            contentValues.put("answer_objectId", mData.get(i).getAnswerBean().getObjectId());
                            contentValues.put("answer_content", mData.get(i).getAnswerBean().getAnswer_content());

                            db.insert("mix_table", null, contentValues);//添加到mix_table表中
                        }
                    } else {
                        //如果所显示的数据>=10，就只存储10个
                        for (int i = 0; i < 10; i++) {

                            ContentValues contentValues = new ContentValues();

                            contentValues.put("questioner_objectId", mData.get(i).getQuestionBean().getQuestioner().getObjectId());
                            contentValues.put("questioner_name", mData.get(i).getQuestionBean().getQuestioner().getUsername());
                            contentValues.put("question_objectId", mData.get(i).getQuestionBean().getObjectId());
                            contentValues.put("question_title", mData.get(i).getQuestionBean().getQuestion_title());
                            contentValues.put("question_description", mData.get(i).getQuestionBean().getQuestion_description());
                            contentValues.put("question_createdAt", mData.get(i).getQuestionBean().getQuestion_createdAt());
                            contentValues.put("answer_objectId", mData.get(i).getAnswerBean().getObjectId());
                            contentValues.put("answer_content", mData.get(i).getAnswerBean().getAnswer_content());

                            db.insert("mix_table", null, contentValues);
                        }
                    }
                }

                mSwipeRefreshLayout.setRefreshing(false);//刷新完毕
            }

            @Override
            public void loadMore() {
                //LoadMore
                if (!isLoadingMore) {
                    isLoadingMore = true;
                    loadMoreQuestions();
                }
            }

            @Override
            public void onLoadMoreDone() {
                isLoadingMore = false;
            }
        });
    }

    /**
     * 使用第三方库——MaterialDialog来预览展示问题。（title&description）
     *
     * @param position 问题item的位置
     */
    private void previewQuestion(int position) {

        contentView = View.inflate(getActivity(), R.layout.question_preview_layout, null);

        final QuestionBean questionPreview = mData.get(position).getQuestionBean();

        questionPreviewTitle = (TextView) contentView.findViewById(R.id.question_preview_title_text);
        questionPreviewTitle.setText(questionPreview.getQuestion_title());

        questionPreviewDesc = (TextView) contentView.findViewById(R.id.question_preview_description_text);
        questionPreviewDesc.setText(questionPreview.getQuestion_description());

        detailText = (TextView) contentView.findViewById(R.id.question_preview_details_text);
        detailText.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent(getActivity(), QuestionDetailActivity.class);
                Bundle bundle = new Bundle();
                bundle.putSerializable("questionBean", questionPreview);
                intent.putExtras(bundle);
                startActivity(intent);
                materialDialog.dismiss();
            }
        });

        OKText = (TextView) contentView.findViewById(R.id.question_preview_ok_text);
        OKText.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                materialDialog.dismiss();
            }
        });

        materialDialog = new MaterialDialog(getActivity()).setView(contentView);
        materialDialog.show();
    }

    /**
     * 下拉加载
     */
    private void findNewQuestions() {

        mSwipeRefreshLayout.setRefreshing(true);
        questionManager.findNewQuestions(getActivity(), mLatestQuestionBean.getQuestion_createdAt(), new QuestionManager.FindNewQuestionsListener() {
            @Override
            public void findNewQuestionsOnSuccess(List<QuestionBean> questionBeans) {

                //因为是根据CreatedAt的降序来排列，所以返回来的questionBeans的第一个是最新的
                questionBeans.remove(questionBeans.size() - 1);

                if (questionBeans.size() == 0) {
                    mSwipeRefreshLayout.setRefreshing(false);
                    Log.i("findNewTenQuestions", "no new data");
                    Snackbar.make(mRecyclerView, "没有新的问题。", Snackbar.LENGTH_SHORT).show();
                } else {
                    //否则就进行新问题的准备和刷新
                    Log.i("findNewTenQuestions", "start setNewData");
                    setNewData(questionBeans);
                }
            }

            @Override
            public void findNewQuestionsOnFailure(String failureMsg) {
                mSwipeRefreshLayout.setRefreshing(false);
                Snackbar.make(mRecyclerView, failureMsg, Snackbar.LENGTH_SHORT).show();
            }
        });
    }

    /**
     * 上拉加载
     */
    private void loadMoreQuestions() {

        questionManager.loadMoreQuestions(getActivity(), mData.get(mData.size() - 1).getQuestionBean().getQuestion_createdAt(), new QuestionManager.LoadMoreQuestionsListener() {
            @Override
            public void loadMoreQuestionsOnSuccess(List<QuestionBean> questionBeans) {
                if (questionBeans.size() == 0) {
                    isLoadingMore = false;
                    Snackbar.make(mRecyclerView, "没有新的问题。", Snackbar.LENGTH_SHORT).show();
                } else {
                    setOldData(questionBeans);
                }
            }

            @Override
            public void loadMoreQuestionsOnFailure(String failureMsg) {

            }
        });
    }

    /**
     * 设置上拉加载获得的旧问题
     *
     * @param questionBeans 上拉加载获取的旧问题
     */
    private void setOldData(List<QuestionBean> questionBeans) {

        mOldDataForChange.clear();
        mOldQuestionDataToBeShown.clear();
        mOldRandomAnswerList.clear();

        for (int i = 0; i < questionBeans.size(); i++) {

            mOldQuestionDataToBeShown.add(i, questionBeans.get(i));

            final int position = i;
            final QuestionBean targetQuestionBean = questionBeans.get(i);

            onlineRequestForAnswerOld++;

            answerManager.findAllAnswersForAll(getActivity(), targetQuestionBean, position, new AnswerManager.FindAllAnswersListener() {
                @Override
                public void findAllAnswersOnSuccess(List<AnswerBean> answers) {
                    if (answers.size() == 0) {
                        AnswerBean answerBean = new AnswerBean();
                        answerBean.setAnswer_of_question(targetQuestionBean);
                        mOldRandomAnswerList.add(answerBean);
                    } else {
                        //把一个随机出来答案保存在暂存答案的List中
                        mOldRandomAnswerList.add(answers.get(new Random().nextInt(answers.size())));
                    }
                    checkOnlineCountForAnswerOld();
                }

                @Override
                public void findAllAnswersOnFailure(String failureMsg) {
                    Log.i("findAnswers", "Failure " + failureMsg);
                }
            });

        }
    }

    /**
     * 检测在上拉加载的时候产生的答案查询网络请求
     */
    private void checkOnlineCountForAnswerOld() {

        if (onlineRequestForAnswerOld == 1) {

            onlineRequestForAnswerOld--;
            for (int i = 0; i < mOldQuestionDataToBeShown.size(); i++) {
                for (int j = 0; j < mOldQuestionDataToBeShown.size(); j++) {
                    if (mOldQuestionDataToBeShown.get(i).getObjectId().equals(mOldRandomAnswerList.get(j).getAnswer_of_question().getObjectId())) {
                        mOldDataForChange.add(new MixQuesAnsBean(mOldQuestionDataToBeShown.get(i), mOldRandomAnswerList.get(j)));
                        break;
                    }
                }
            }
            mAdapter.addOldData(mOldDataForChange);


        } else {
            onlineRequestForAnswerOld--;
        }

    }

    /**
     * 设置下拉加载获得的新问题
     *
     * @param questionBeans 下拉加载获取的新问题
     */
    private void setNewData(final List<QuestionBean> questionBeans) {

        Log.i("setNewData", "begin");

        mDataForChange.clear();// 清空 要显示新的MixQuesAnsBeans 的List
        mRandomAnswerList.clear();// 清空 存储要显示新的Questions对应随机的一个答案 的List
        mQuestionDataToBeShown.clear();// 清空 存储要显示新的Questions 的List

        for (int i = 0; i < questionBeans.size(); i++) {

            //questionBeans.get(i).setQuestion_createdAt(questionBeans.get(i).getCreatedAt());

            mQuestionDataToBeShown.add(i, questionBeans.get(i));

            final int position = i;
            Log.i("setNewData", "position = " + position);
            final QuestionBean targetQuestionBean = questionBeans.get(i);

            //每进行一次获取问题所有答案的网络请求 flag+1
            onlineRequestForAnswerNew++;

            Log.i("setNewData", "onlineRequestForAnswerNew = " + onlineRequestForAnswerNew);

            answerManager.findAllAnswersForAll(getActivity(), targetQuestionBean, position, new AnswerManager.FindAllAnswersListener() {

                int pos = position;

                @Override
                public void findAllAnswersOnSuccess(List<AnswerBean> answers) {
                    Log.i("findAnswers", "Success mDataForChange size = " + mDataForChange.size());
                    Log.i("findAnswers", "Success; position = " + pos);
                    //如果是新问题没有答案呢？
                    if (answers.size() == 0) {
                        AnswerBean answerBean = new AnswerBean();
                        answerBean.setAnswer_of_question(targetQuestionBean);
                        mRandomAnswerList.add(answerBean);
                    } else {
                        //把一个随机出来答案保存在暂存答案的List中
                        mRandomAnswerList.add(answers.get(new Random().nextInt(answers.size())));
                    }
                    //检测当前还没有完成的 获取问题所有答案的网络请求 数量
                    checkOnlineCountForAnswerNew();
                }

                @Override
                public void findAllAnswersOnFailure(String FailureMSG) {
                    Log.i("findAnswers", "Failure " + FailureMSG);
                }
            });
        }
    }

    /**
     * 检测在下拉加载的时候产生的答案查询网络请求
     */
    private void checkOnlineCountForAnswerNew() {

        if (onlineRequestForAnswerNew == 1) {
            // 如果 获取问题所有答案的网络请求 的数量为1
            // 就可以作配对形成最终mDataForChange

            //先把自身请求去掉
            onlineRequestForAnswerNew--;

            isGetFromDatabase = false;

            Log.i("refreshing", "mQuestionDataToBeShown size " + mQuestionDataToBeShown.size());
            Log.i("refreshing", "mRandomAnswerList size " + mRandomAnswerList.size());

            for (int i = 0; i < mQuestionDataToBeShown.size(); i++) {
                //根据要显示的新问题List的来配对随机的一个Answer

                Log.i("mQuestionDataToBeShown", "----------> " + i + " time -------------------> " + mQuestionDataToBeShown.get(i).getCreatedAt());

                for (int j = 0; j < mQuestionDataToBeShown.size(); j++) {

                    Log.i("refreshing", "questionID " + mQuestionDataToBeShown.get(i).getObjectId());
                    Log.i("refreshing", "answerID " + mRandomAnswerList.get(j).getAnswer_of_question().getObjectId());

                    if (mQuestionDataToBeShown.get(i).getObjectId().equals(mRandomAnswerList.get(j).getAnswer_of_question().getObjectId())) {
                        //如果随机答案List中的第J个答案的question objectId跟问题id相同则配对形成新的MixQuesAnsBean

                        Log.i("mQuestionDataToBeShown", "----------> " + i + " title -------------------> " + mQuestionDataToBeShown.get(i).getQuestion_title());
                        Log.i("mQuestionDataToBeShown", "----------> " + i + " answer -------------------> " + mRandomAnswerList.get(j).getAnswer_content());

                        //把新的MixQuesAnsBean以Question的CreatedId降序的形式添加到 要显示新的MixQuesAnsBeans 的List
                        mDataForChange.add(i, new MixQuesAnsBean(mQuestionDataToBeShown.get(i), mRandomAnswerList.get(j)));

                        break;//停止当前子循环
                    }
                }
            }

            Log.i("refreshing", "mDataForChange size " + mDataForChange.size());
            // 可以刷新列表
            // 调用addData方法
            mAdapter.addData(mDataForChange);
            // 置顶显示第一个item
            mRecyclerView.scrollToPosition(0);
            // 配置将显示了最新的question
            mLatestQuestionBean = mQuestionDataToBeShown.get(0);
            Log.i("setNewData", "set new data done!!! ------------------------>" + mLatestQuestionBean.getCreatedAt());
        } else {
            //如果 获取问题所有答案的网络请求 的数量不为1
            //则还有网络请求正在进行
            //把自身这个完成的请求去掉
            onlineRequestForAnswerNew--;
            Log.i("checkOnlineCountForAnswerNew", "there is/are " + onlineRequestForAnswerNew + " request left");
        }

    }

    /**
     * 程序第一次打开时的刷新操作：
     * 如果有缓存就加载缓存的内容，没有的话就进行网络请求
     */
    private void firstTimeRefresh() {

        Cursor cursor = db.rawQuery("select * from mix_table", null);

        if (cursor.getCount() == 0) {
            cursor.close();
            Log.i("all first time refresh", "mix_table is null");
            Toast.makeText(getActivity(), "null", Toast.LENGTH_LONG).show();
            mSwipeRefreshLayout.setRefreshing(true);
            questionManager.firstTimeFindNewQuestions(getActivity(), new QuestionManager.FindNewQuestionsListener() {
                @Override
                public void findNewQuestionsOnSuccess(List<QuestionBean> questionBeans) {
                    if (questionBeans.size() != 0) {
                        setNewData(questionBeans);
                    } else {
                        mSwipeRefreshLayout.setRefreshing(false);
                        Snackbar.make(mSwipeRefreshLayout, "没有新的问题", Snackbar.LENGTH_SHORT).show();
                    }

                }

                @Override
                public void findNewQuestionsOnFailure(String failureMsg) {
                    mSwipeRefreshLayout.setRefreshing(false);
                    Snackbar.make(mSwipeRefreshLayout, failureMsg, Snackbar.LENGTH_SHORT).show();
                }
            });
        } else {
            Log.i("all first time refresh", "mix_table isn't null ------------>" + cursor.getCount());
            mSwipeRefreshLayout.setRefreshing(true);

            String[] cols = cursor.getColumnNames();

            while (cursor.moveToNext()) {
                QuestionBean questionBean = new QuestionBean();
                AnswerBean answerBean = new AnswerBean();
                UserBean userBean = new UserBean();
                for (String ColumnName : cols) {
                    Log.i("columnName", "--------------------->" + ColumnName + ":" + cursor.getString(cursor.getColumnIndex(ColumnName)));
                    switch (ColumnName) {
                        case "questioner_objectId":
                            userBean.setObjectId(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "question_objectId":
                            questionBean.setObjectId(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "questioner_name":
                            userBean.setUsername(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "question_title":
                            questionBean.setQuestion_title(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "question_description":
                            questionBean.setQuestion_description(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "answer_objectId":
                            answerBean.setObjectId(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "answer_content":
                            answerBean.setAnswer_content(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                        case "question_createdAt":
                            questionBean.setQuestion_createdAt(cursor.getString(cursor.getColumnIndex(ColumnName)));
                            break;
                    }
                }
                questionBean.setQuestioner(userBean);
                mQuestionDataToBeShown.add(questionBean);
                mDataForChange.add(new MixQuesAnsBean(questionBean, answerBean));
            }

            /*for (int count = 0; count < 10; count++) {
                Log.i("mDataForChange", "item " + count + " " + mDataForChange.get(count).getQuestionBean().getQuestion_title());
            }*/

            cursor.close();
            mAdapter.addData(mDataForChange);
            mRecyclerView.scrollToPosition(0);
            mLatestQuestionBean = mQuestionDataToBeShown.get(0);
        }
    }

    /**
     * 定义public刷新方法让MainActivity来调用
     */
    public void callToRefreshData() {
        if (!mSwipeRefreshLayout.isRefreshing()) {
            findNewQuestions();
        }
    }

    /**
     * 在fragment（程序）关闭时关闭数据库
     */
    @Override
    public void onDestroy() {
        db.close();
        super.onDestroy();
    }
}
